#region Copyright Notices
// This library is free software; you can redistribute it and/or
// modify it under the terms of the GNU Library General Public
// License as published by the Free Software Foundation; either
// version 2 of the License, or (at your option) any later version.
//
// This library is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
// Library General Public License for more details.
// 
// You should have received a copy of the GNU Library General Public
// License along with this library; if not, write to the Free
// Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
#endregion

using System;
using System.Diagnostics.CodeAnalysis;

namespace Yarr
{
	/// <summary>
	/// Built in macros
	/// </summary>
    [Package("system")]
	internal static class Macros
	{
        // Macros 

        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]
        [Eval("atomp")]     internal static string AtomP =       "(fn (a) (or (== a null) (is Yarr.Symbol a) (!= (System.Type.GetTypeCode (typeof a)) TypeCode.Object)))";

        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]
        [Eval("bind-dispatch-character")]
                            internal static string BindDispatchChar =   
                                                                 "(macro (disp chr f) `(*readtable*.SetDispatchCharacter ,disp ,chr ,f))";

        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]
        [Eval("bind-macro-character")]
                            internal static string BindMacroChar =      
                                                                 "(macro (chr f) `(*readtable*.SetMacroCharacter ,chr ,f))";

        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]
        [Eval("defevent")]
        internal static string DefEvent = "(macro (eventname target args &body body) `(do (handle-event ,target (symbol-name ',eventname) (fn ,args ,@body)) '(,target ,eventname)))";

        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]
        [Eval("defun")]
        internal static string Defun = "(macro (name args &body body) `(do (= ,name (fn ,args ,@body)) ',name))";

        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]
        [Eval("defmacro")]

        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]
        internal static string DefMacro = "(macro (name args &body body) `(do (= ,name (macro ,args ,@body)) ',name))";

        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]
        [Eval("defsetf")]
        internal static string DefSetf = "(macro (name args &body body) `(do (bind-setf-method ,name (fn ,args ,@body)) ',name))";

        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]
        [Eval("evenp")]
        internal static string EvenP = "(fn (n) (and (numberp n) (not (mod n 2))))";

        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]
        [Eval("listp")]
        internal static string ListP = "(fn (l) (or (== l null) (is Yarr.Cons l)))";

        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]
        [Eval("make-array")]
                            internal static string MakeArray =   "(macro (type &rest args) `(System.Array.CreateInstance ,type ,@args))";

        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]
        [Eval("make-hashtable")]
                            internal static string MakeHashTable =
                                                                 "(macro (&key (key system.string) (value system.object) (size 10)) `(new (type 'System.Collections.Generic.Dictionary ,key ,value) ,size))";

        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]
        [Eval("make-stack")]
                            internal static string MakeStack =   "(macro (&key (of system.object) (size 10)) `(new (type 'System.Collections.Generic.Stack ,of) ,size))";

        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]
        [Eval("make-queue")]
                            internal static string MakeQueue =   "(macro (&key (of system.object) (size 10)) `(new (type 'System.Collections.Generic.Queue ,of) ,size))";

        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]
        [Eval("make-list")]
        internal static string MakeList = "(macro (&key (of system.object) (size 10)) `(new (type 'System.Collections.Generic.List ,of) ,size))";

        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]
        [Eval("mapcan")]
        internal static string MapCan = "(macro (func &rest args) `(apply nconc (map ,func ,@args)))";

        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]
        [Eval("mapcon")]
        internal static string MapCon = "(macro (func &rest args) `(apply nconc (maplist ,func ,@args)))";

        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]

        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]
        [Eval("minusp")]
        internal static string MinusP = "(fn (n) (and (numberp n) (< n 0)))";

        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]
        [Eval("oddp")]
        internal static string OddP = "(fn (n) (and (numberp n) (mod n 2)))";

        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]
        [Eval("plusp")]
        internal static string PlusP = "(fn (n) (and (numberp n) (> n 0)))";

        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]
        [Eval("pop")]
        internal static string Pop = "(macro (lst) `(let :temp: (car ,lst) (= ,lst (cdr ,lst)) :temp:))";

        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]
        [Eval("push")]
        internal static string Push = "(macro (obj lst) `(= ,lst (cons ,obj ,lst)))";

        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]
        [Eval("unbind-dispatch-character")]
                            internal static string UnbindDispatchChar = 
                                                                 "(macro (disp chr) `(*readtable*.SetDispatchCharacter ,disp ,chr (the Yarr.Closure null)))";

        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]
        [Eval("unbind-macro-character")]
        internal static string UnbindMacroChar =                 "(macro (chr) `(*readtable*.SetMacroCharacter  ,chr (the Yarr.Closure null)))";
        
        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]
        [Eval("when")]
        internal static string When = "(macro (test &body body) `(if ,test (do ,@body)))";

        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]
        [Eval("zerop")]
        internal static string ZeroP = "(fn (n) (and (numberp n) (== n 0)))";

        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]
        [Eval("*e*")]
        internal static double E = Math.E;

        [SuppressMessage("Microsoft.Performance", "CA1823:AvoidUnusedPrivateFields")]
        [Eval("*pi*")]
        internal static double PI = Math.PI;
    }
}
